package com.wdb007.venus.web.api.rpc.impl;

import java.math.BigDecimal;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.util.ObjectUtils;

import com.alibaba.fastjson.JSON;
import com.wdb.exchange.model.ActivityLoginModel;
import com.wdb.exchange.model.InitBookShelfInfoModel;
import com.wdb.exchange.model.PresentAmountModel;
import com.wdb.exchange.model.PresentVIPModel;
import com.wdb.exchange.model.RespModel;
import com.wdb.exchange.model.ReturnBookCount;
import com.wdb.exchange.model.User;
import com.wdb.exchange.model.UserReadRecordModel;
import com.wdb.exchange.service.ApiService;
import com.wdb007.venus.svc.biz.manager.ConfigInfoManager;
import com.wdb007.venus.svc.biz.utils.DateFormatUtil;
import com.wdb007.venus.svc.dal.book.dao.BookGridDAO;
import com.wdb007.venus.svc.dal.book.dao.BookShelfDAO;
import com.wdb007.venus.svc.dal.book.model.BookGridDO;
import com.wdb007.venus.svc.dal.book.model.BookShelfDO;
import com.wdb007.venus.svc.facade.BookgridService;
import com.wdb007.venus.svc.facade.CouponService;
import com.wdb007.venus.svc.facade.UserService;
import com.wdb007.venus.svc.facade.WxAppHDService;
import com.wdb007.venus.svc.facade.constant.BizConstants;
import com.wdb007.venus.svc.facade.constant.RspCodeEnum;
import com.wdb007.venus.svc.facade.exception.BizException;
import com.wdb007.venus.svc.facade.exception.SysException;
import com.wdb007.venus.svc.facade.user.model.SmsVerifactionDTO;
import com.wdb007.venus.svc.facade.user.model.UserAccessLogDTO;
import com.wdb007.venus.svc.facade.wxapp.model.SingleReadRecordDTO;

@Component
public class ApiServiceImpl implements ApiService {
	private final static Logger logger = LoggerFactory.getLogger(ApiServiceImpl.class);
	@Autowired
	private UserService userService;
	@Autowired
	CouponService couponService;
	@Autowired
	BookgridService bookgridService;
	@Autowired
	private WxAppHDService wxAppHDService;
	
	@Autowired
	private BookShelfDAO bookShelfDAO;
	@Autowired
	private BookGridDAO bookGridDAO;
	
	@Autowired
	private ConfigInfoManager configInfoManager;
	
	@Override
	public String echo(String s) {
		return s;
	}

	@Override
	public User getUserById(String s) {
		return null;
	}
	@Override
	public ReturnBookCount getCurrentDateReturnBookCount(String userid) {
		ReturnBookCount count = new ReturnBookCount();
		try {
			count.setCount(bookgridService.getCurrentDateReturnBookCount(Long.valueOf(userid)));
		} catch (Exception e) {
			e.printStackTrace();
		}
		return count;
	}

	@Override
	public User getWxUserinfoByToken(String usertoken, Long userid, String appid) {
		logger.info("api mq request params:usertoken-{},userid-{},appid-{}", usertoken, userid, appid);
		User user = new User();
		user.code = 0;
		user.message = "操作成功";
		try {
			//如果存在userid，直接checktoken是否正确
			if (!isEmpty(userid)) {
				String checktoken = userService.getTokenByChannelAndUserId(userid, BizConstants.CHANNEL_WX);
				//token验证失败
				if (!usertoken.equals(checktoken)) {
					user.code = RspCodeEnum.USER_TOKEN_IS_UNVALID.getRspCode();
					user.message = RspCodeEnum.USER_TOKEN_IS_UNVALID.getRspMsg();
					return user;
				}
			}
			//直接请求
			user.detail = userService.getWxUserinfoByTokenV2(usertoken, userid, appid);
		} catch (Exception e) {
			e.printStackTrace();
			user.code = RspCodeEnum.USER_TOKEN_IS_UNVALID.getRspCode();
			user.message = RspCodeEnum.USER_TOKEN_IS_UNVALID.getRspMsg();
			return user;
		}
		logger.info("api mq request end:usertoken-{},user[{}]",usertoken,user);
		return user;
	}

	protected boolean isEmpty(Object obj) {
		if (ObjectUtils.isEmpty(obj) || "null".equals(obj) || "undetined".equals(obj)) {
			return true;
		}
		return false;
	}

	@Override
	public Map<String, Object> couponBookShelfInfo(String couponRuleId) {
		Map<String, Object> result = couponService.couponBookShelfInfo(couponRuleId);
		logger.info("couponBookShelfInfo:{}",result);
		return result;
	}

	@Override
	public RespModel activityLogin(ActivityLoginModel activityLogin) {
		logger.info("api mq rpc activityLogin's param: {}", JSON.toJSONString(activityLogin));
		RespModel respModel = success();
		try {
			checkIsNull(activityLogin.getMobileNo(), "mobileNo");
			checkIsNull(activityLogin.getVerifyCode(), "verityCode");
			checkIsNull(activityLogin.getActivityPartner(), "activityPartner");
			
			SmsVerifactionDTO smsVerifaction = new SmsVerifactionDTO();
			smsVerifaction.setMobileNo(activityLogin.getMobileNo());
			smsVerifaction.setSmsCode(activityLogin.getVerifyCode());
			
			UserAccessLogDTO accessLog = new UserAccessLogDTO();
			accessLog.setPartner(activityLogin.getActivityPartner());
			
			userService.login(smsVerifaction, accessLog, null);
		}catch(Exception e) {
			respModel = failed(e);
			logger.error("activityLogin err", e);
		}
		logger.info("api mq rpc activityLogin's result: {}", JSON.toJSONString(respModel));
		return respModel;
	}

	@Override
	public RespModel presentAmount(PresentAmountModel presentAmount) {
		logger.info("api mq rpc presentAmount's param: {}", JSON.toJSONString(presentAmount));
		RespModel respModel = success();
		try {
			String mobile_no = presentAmount.getMobileNo();
			String amount = presentAmount.getAmount()+"";
			wxAppHDService.presentAmount(mobile_no, amount);
		} catch (BizException e) {
			respModel = failed(e);
			logger.error("用户加钱presentAmount error", e);
		}
		logger.info("api mq rpc presentAmount's result: {}", JSON.toJSONString(respModel));
		return respModel;
	}

	@Override
	public RespModel presentVIP(PresentVIPModel presentVIP) {
		logger.info("api mq rpc presentVIP's param: {}", JSON.toJSONString(presentVIP));
		RespModel respModel = success();
		
		try {
			checkIsNull(presentVIP.getMobileNo(), "mobile_no");
			checkIsNull(presentVIP.getVipType(), "vip_type");
			wxAppHDService.presentVIP(presentVIP.getMobileNo(), presentVIP.getVipType(), presentVIP.getDays());
		}catch(Exception e) {
			respModel = failed(e);
			logger.error("用户加月卡天数presentVIP error", e);
		}
		logger.info("api mq rpc presentVIP's result: {}", JSON.toJSONString(respModel));
		return respModel;
	}

	@Override
	public RespModel userVIPEndDate(String mobileNo) {
		logger.info("api mq rpc userVIPEndDate's param ===mobileNo:[{}]", mobileNo);
		RespModel respModel = success();
		try {
			String vipEndDate = userService.getUserVIPEndDate(mobileNo);
			Map<String, Object> details = new HashMap<String, Object>();
			details.put("end_date", vipEndDate);
			respModel.setDetails(details );
		} catch (BizException e) {
			respModel = failed(e);
			logger.error("获取userVIPEndDate error", e);
		}
		logger.info("api mq rpc userVIPEndDate's result : {}", JSON.toJSONString(respModel));
		return respModel;
	}

	@Override
	public RespModel userReadRecord(Long userid) {
		logger.info("api mq rpc userReadRecord's param ===userid:[{}]", userid);
		RespModel respModel = success();
		try {
			checkIsNull(userid, "userid");
			SingleReadRecordDTO singleUserReadRecord = wxAppHDService.getSingleUserReadRecord(userid);
			UserReadRecordModel recordModel = new UserReadRecordModel();
			recordModel.setMonthRecord(singleUserReadRecord.getMonth_record());
			recordModel.setWeekRecord(singleUserReadRecord.getWeek_record());
			recordModel.setTotalRead(singleUserReadRecord.getTotal_record());
			Map<String, Object> details = new HashMap<String, Object>();
			details.put("userReadRecord", recordModel);
			respModel.setDetails(details);
		} catch (BizException e) {
			respModel = failed(e);
			logger.error("userReadRecord's error", e);
		}
		logger.info("api mq rpc userReadRecord's result : {}", JSON.toJSONString(respModel));
		return respModel;
	}
	
	private RespModel success() {
		RespModel respModel = new RespModel();
		respModel.setCode(0);
		respModel.setMsg("操作成功");
		return respModel;
	}
	
	private RespModel failed(Exception e) {
		RespModel respModel = new RespModel();
		
		if(e instanceof BizException) {
			BizException bizRuntimeException = (BizException) e;
			if(bizRuntimeException.getErrorCode() == 0) {
				respModel.setCode(0);
				respModel.setMsg("操作成功");
			}else if(bizRuntimeException.getErrorCode() == 1010080002) {
				respModel.setCode(0);
				respModel.setMsg("操作成功");
			}else {
				respModel.setCode(bizRuntimeException.getErrorCode());
				respModel.setMsg(bizRuntimeException.getErrorMsg());
			}
		}else if(e instanceof SysException) {
			SysException sysRuntimeException = (SysException) e;
			respModel.setCode(sysRuntimeException.getErrorCode());
			respModel.setMsg(sysRuntimeException.getErrorMsg());
		}else {
			respModel.setCode(1010080099);
			respModel.setMsg("系统异常，请联系管理员");
		}
		return respModel;
	}
	protected void checkIsNull(Object obj, String key) throws BizException {
		if(ObjectUtils.isEmpty(obj) || "undefined".equals(obj) || "null".equals(obj)) {
			throw new BizException(RspCodeEnum.PARAM_CHECK_IS_NULL.setRspMessage(key));
		}
	}

	@Override
	public RespModel initBookshelfInfo(InitBookShelfInfoModel initBookshelfInfo) {
		logger.info("api mq rpc initBookshelfInfo's param: {}", JSON.toJSONString(initBookshelfInfo));
		RespModel respModel = success();
		try {
			checkIsNull(initBookshelfInfo.getBookShelfCode(), "bookShelfCode");
			checkIsNull(initBookshelfInfo.getBookShelfArea(), "bookShelfArea");
			checkIsNull(initBookshelfInfo.getAddress(), "address");
			checkIsNull(initBookshelfInfo.getGridNum(), "gridNum");
			checkIsNull(initBookshelfInfo.getLatitude(), "latitude");
			checkIsNull(initBookshelfInfo.getLongtiude(), "longtiude");
			checkIsNull(initBookshelfInfo.getModel(), "model");
			checkIsNull(initBookshelfInfo.getVer(), "ver");
			checkIsNull(initBookshelfInfo.getSortBy(), "sortBy");
			
			BookShelfDO bookShelf = bookShelfDAO.get(initBookshelfInfo.getBookShelfCode());
			if(null != bookShelf) {
				throw new BizException(RspCodeEnum.BOOKSHELF_IS_ALREADY_EXISTS);
			}
			//查找一个默认策略:
			String policyRule = configInfoManager.getValue("default_policy_rule");
			String gridImg = configInfoManager.getValue("default_grid_img_url");
			BookShelfDO newBookShelf = new BookShelfDO();
			newBookShelf.setAddress(initBookshelfInfo.getAddress());
			newBookShelf.setArea(initBookshelfInfo.getBookShelfArea());
			newBookShelf.setAvailable(1);
			newBookShelf.setCode(initBookshelfInfo.getBookShelfCode());
			newBookShelf.setCreateTime(new Date());
			newBookShelf.setInstallTime(DateFormatUtil.formatDateTime(new Date()));
			newBookShelf.setLatitude(new BigDecimal(initBookshelfInfo.getLatitude()));
			newBookShelf.setLongitude(new BigDecimal(initBookshelfInfo.getLongtiude()));
			newBookShelf.setModel(initBookshelfInfo.getModel());
			newBookShelf.setVer(initBookshelfInfo.getVer());
			newBookShelf.setSortBy(Integer.parseInt(initBookshelfInfo.getSortBy()));
			newBookShelf.setPolicyRule(policyRule);
			bookShelfDAO.insert(newBookShelf);
			
			for(int i=1; i<= initBookshelfInfo.getGridNum(); i++) {
				BookGridDO bookGrid = new BookGridDO();
				bookGrid.setAvailable(1);
				bookGrid.setBookgridCode(initBookshelfInfo.getBookShelfCode() + "0" + i);
				bookGrid.setBookgridImg(gridImg);
				bookGrid.setBookshelfCode(initBookshelfInfo.getBookShelfCode());
				bookGrid.setCreateTime(new Date());
				bookGrid.setDamageReport(0);
				bookGrid.setLockStatus(5);
				bookGrid.setSerialNumber(i);
				bookGridDAO.insert(bookGrid);
			}
		}catch(Exception e) {
			respModel = failed(e);
			logger.error("初始化书柜报错", e);
		}
		
		return respModel;
	}
	
}
